//
//  VCDownloadManger.m
//  VC
//
//  Created by 肖康龙 on 2017/8/30.
//  Copyright © 2017年 vsoontech. All rights reserved.
//

#import "VCDownloadManger.h"
#import "VCInformationMoudle.h"
#import "VCDownloadTs.h"
#import "VCTsDataModel.h"
#import "VCDowmload.h"
#import "AuxiliaryModel.h"
#import "VCVideoPlayerManager.h"

#import <HTTPServer.h>
#import <DDTTYLogger.h>
#import "VCDownloadHTTPConnection.h"
#import <AFNetworking.h>
#import "VCDebugView.h"


#include <notify.h>//检查锁屏

@interface VCDownloadManger ()<VCDownloadTsDelegate>
/**本地服务器*/
@property (strong, nonatomic) HTTPServer *httpServer;
/**播放的ID*/
@property (strong, nonatomic)NSString *resourceID;
/**服务器端口*/
@property (nonatomic,assign) NSInteger serverProt;
/**是否有息屏过*/
@property (nonatomic,assign)BOOL isScreenOff;
/**有多少个主机*/
@property (nonatomic,assign)NSUInteger hostCount;
/**下载器 用来下载ts*/
@property (nonatomic,strong)NSMutableArray *array_Ts;
/**加速下载的task*/
@property (nonatomic,strong)NSMutableArray *array_accelerate;

/**host打通道失败,要更换给其他下载的ts序号*/
@property (nonatomic,strong)NSMutableArray *array_tsSerial;
/**host请求数据失败,在当前废弃的host*/
@property (nonatomic,strong)NSMutableArray *array_tsHost;
/**发送报告的定时器*/
@property (nonatomic,strong)NSTimer *timer_Report;

/**下载到第几个*/
@property (nonatomic,assign)int downloadNum;
/**播放器播到第几个*/
@property (nonatomic,assign)int PlayNnm;
/**播放到的时间 毫秒*/
@property (nonatomic,assign)NSInteger seekVod;

/**网络状态*/
@property (nonatomic,assign)AFNetworkReachabilityStatus networkReachabilityStatus;

/**辅助下载的ts*/
@property (nonatomic,strong)NSMutableData *auxiliaryData;
/**辅助下载的片段*/
@property (nonatomic,strong)NSMutableArray *array_auxiliary;

/**上报*/
/**播放时长*/
@property (nonatomic,assign)NSUInteger playTimer;
/**总有效流量*/
@property (nonatomic,assign)NSUInteger vcSize;
/**加速流量*/
@property (nonatomic,assign)NSUInteger accelSize;
/**每一个host的流量监听*/
@property (nonatomic,strong)NSMutableArray *array_vc;
/**调试页面*/
@property (nonatomic,strong)VCDebugView *debugView;
/**调试的定时器 100毫秒一次*/
@property (nonatomic,strong)NSTimer *timer_debug;
/**是否正在暂停*/
@property (nonatomic,assign)BOOL isSuspend;
/**已下载时长*/
@property (nonatomic,assign)NSTimeInterval alreadyDownloadedTime;
/**已播放时长*/
@property (nonatomic,assign)NSTimeInterval alreadyPlayTime;
/**持续播放不卡顿的时长*/
@property (nonatomic,assign)NSTimeInterval noCatonTime;
/**卡顿次数*/
@property (nonatomic,assign)int catonNum;
/**暂停播放的时长*/
@property (nonatomic,assign)NSTimeInterval catonTimer;
/**播放器*/
//@property (nonatomic,strong)id <IJKMediaPlayback> player;



/**是否正在请求ts列表*/
@property (nonatomic,assign)BOOL isRequestTsList;
/**是否用加速接口请求ts*/
@property (nonatomic,assign)BOOL isSpeedDownloadTS;
/**是否因为缓存时间太小请求加速接口*/
@property (nonatomic,assign)BOOL isSpeedCacheSmall;


/**总的缓存时间*/
@property (nonatomic,assign)NSTimeInterval totalCacheTime;
/**需要缓存的时间*/
@property (nonatomic,assign)NSTimeInterval needCacheTime;
/**切换为cdn的临界点*/
@property (nonatomic,assign)NSTimeInterval changeCDNPoint;
/**下一个ts列表起始时间*/
@property (nonatomic,assign)NSTimeInterval nextStartSec;
@end

//static void handleLockStateNotification(CFNotificationCenterRef center, void *observer, CFStringRef name, const void *object, CFDictionaryRef userInfo)
//{
//    uint64_t state;
//    int token;
//    notify_register_check("com.apple.springboard.lockstate", &token);
//    notify_get_state(token, &state);
//    notify_cancel(token);
//    if ((uint64_t)1 == state)
//    {
//        NSLog(@"********锁屏**********");
//        [VCDownloadManger DownloadManger].isScreenOff = YES;
//        AppDelegate *appDelegate = (AppDelegate *)[UIApplication sharedApplication].delegate;
//        if (appDelegate.isEnterBackground) {
//            [PPCore logout];
//        }else{
//            [[NSNotificationCenter defaultCenter] postNotificationName:NotificationOnLock object:nil];
//        }
//    }
//    else
//    {
//        [[NSNotificationCenter defaultCenter] postNotificationName:NotificationOffMayHaveUnlock object:nil];
//        NSLog(@"********解锁**********");
//    }
//}

static void ListeningScreenLockState(CFNotificationCenterRef center,void* observer,CFStringRef name,const void* object,CFDictionaryRef userInfo)

{

    NSString* screenState = (__bridge NSString*)name;
    if ([screenState isEqualToString:(__bridge  NSString*)NotificationOff]) {

        VCNSLog(@"********锁屏**********");
        [VCDownloadManger DownloadManger].isScreenOff = YES;
    } else {
        VCNSLog(@"********解锁**********");
    }

}

@implementation VCDownloadManger
/**初始化数据,主要是请求加解密数据*/
+(void)initData{

    
    VCInformationMoudle *moudle = [[VCInformationMoudle alloc] init];
    [moudle getKeyWithsucceed:^(id data) {
    } fail:^(NSError *error) {
    }];
//    [VCDownloadManger DownloadManger];
}
/**单利*/
+(VCDownloadManger *)DownloadManger{
    static VCDownloadManger *manger;
    if (manger == nil) {
        manger = [[VCDownloadManger alloc] init];
    }
    return manger;
}


- (instancetype)init
{
    self = [super init];
    if (self) {
        static BOOL isAddObserver;
        if (!isAddObserver) {
            isAddObserver = YES;
            CFNotificationCenterAddObserver(CFNotificationCenterGetDarwinNotifyCenter(), NULL, ListeningScreenLockState, NotificationOff, NULL, CFNotificationSuspensionBehaviorDeliverImmediately);

            CFNotificationCenterAddObserver(CFNotificationCenterGetDarwinNotifyCenter(), NULL, ListeningScreenLockState, NotificationOn, NULL, CFNotificationSuspensionBehaviorDeliverImmediately);
            //锁屏
//            CFNotificationCenterAddObserver(CFNotificationCenterGetDarwinNotifyCenter(), NULL, handleLockStateNotification, CFSTR("com.apple.springboard.lockstate"), NULL, CFNotificationSuspensionBehaviorDeliverImmediately);
        }
        /*回到前台*/
        [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(willEnterForeground:) name:UIApplicationWillEnterForegroundNotification object:nil];
        /*进入后台*/
        [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(willEnterBackground:) name:UIApplicationDidEnterBackgroundNotification object:nil];
        /*host请求不成功*/
        [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(changeNewHostDownload:) name:VCDownloadTunnelOpenFailNotification object:nil];
        /**播放器请求的ts*/
        [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(DownloadPlayerTs:) name:VCDownloadSendDownloadNotification object:nil];
        /**播放器正在请求的ts*/
        [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(playGetTs:) name:VCDownloadPlayGetTsNotification object:nil];
        
        
        /**删除文件*/
        NSString *path_root = [[[NSSearchPathForDirectoriesInDomains(NSDocumentDirectory,NSUserDomainMask,YES) objectAtIndex:0] stringByAppendingPathComponent:@"Downloads"] stringByAppendingPathComponent:@"movie1"];
        [VCInformationTool deleteFileWithPath:path_root];
        
        self.needCacheTime = 50000;//50秒
        self.changeCDNPoint = 10000;//10秒
    }
    return self;
}
-(void)dealloc{
    [self stopDownload];
//    [self.player shutdown];
//    self.player = nil;
    [[NSNotificationCenter defaultCenter] removeObserver:self];

    [VCInformationTool saveTSFileWithTsName:nil isReset:YES tsNum:0];
}

-(NSTimer *)timer_Report{
    if (_timer_Report == nil) {
        [[AFNetworkReachabilityManager sharedManager] startMonitoring];
        
        __VCWeakSelf
        _timer_Report = [NSTimer scheduledTimerWithTimeInterval:REPORT_TIME repeats:YES block:^(NSTimer * _Nonnull timer) {
            [[NSNotificationCenter defaultCenter] postNotificationName:VCDownloadReportNotification object:nil];
            weakSelf.playTimer++;
            weakSelf.networkReachabilityStatus = [AFNetworkReachabilityManager sharedManager].networkReachabilityStatus;
            
            if (weakSelf.array_Ts.count < 1 && (weakSelf.networkReachabilityStatus == AFNetworkReachabilityStatusReachableViaWiFi || weakSelf.networkReachabilityStatus == AFNetworkReachabilityStatusReachableViaWWAN)) {
                [weakSelf createTsNewDownload];//检查是否要重新来刷新
                
//                [weakSelf checkDownloadFial];//暂时感觉没什么用
                
            }
            
//            for (VCDownloadTs *ts in self.array_Ts) {
//                if (ts.isFree) {
//                    if(![weakSelf checkFailureWithdownload:ts]) break;//没有要帮忙的
//                }
//            }
            
            //重新检查是否需要继续下载
            [weakSelf selectDownloadModelWithIndex:weakSelf.downloadNum];
        }];
        [[NSRunLoop mainRunLoop] addTimer:_timer_Report forMode:NSRunLoopCommonModes];
    }
    return _timer_Report;
}

-(NSMutableArray *)array_Ts{
    if (_array_Ts == nil) {
        _array_Ts = [NSMutableArray array];
    }
    return _array_Ts;
}

-(NSMutableArray *)array_tsSerial{
    if (_array_tsSerial == nil) {
        _array_tsSerial = [NSMutableArray array];
    }
    return _array_tsSerial;
}

-(NSMutableArray *)array_tsHost{
    if (_array_tsHost == nil) {
        _array_tsHost = [NSMutableArray array];
    }
    return _array_tsHost;
}
-(NSMutableArray *)array_vc{
    if (_array_vc == nil) {
        _array_vc = [NSMutableArray array];
        NSArray *array = [self.dict objectForKey:@"hostList"];
        for (NSDictionary *dict in array) {
            NSMutableDictionary *dict_M= [NSMutableDictionary dictionary];
            [dict_M setObject:[dict objectForKey:@"host"] forKey:@"host"];
            [dict_M setObject:@0 forKey:@"tSize"];
            [dict_M setObject:@0 forKey:@"vSize"];
            [_array_vc addObject:dict_M];
        }
    }
    return _array_vc;
}

-(NSMutableArray *)array_auxiliary{
    if (_array_auxiliary == nil) {
        _array_auxiliary = [NSMutableArray array];
    }
    return _array_auxiliary;
}


-(void)setCurrentPlaybackTime:(NSTimeInterval)currentPlaybackTime{
    _currentPlaybackTime = currentPlaybackTime;
    
    [VCInformationTool setPlayerChangeTime:YES];//设置为正在切换时间
    [self.array_Ts makeObjectsPerformSelector:@selector(stopDownloadTs)];//停止之前所有的下载
    self.dict = nil;//清除列表
    self.totalCacheTime = 0;//清理缓存时间
    [VCInformationTool setVC_sequence:0];//清除序列号
    self.downloadNum = 0;
    [self.array_accelerate makeObjectsPerformSelector:@selector(cancel)];//清除加速接口
    [self.array_accelerate removeAllObjects];
    self.isSpeedDownloadTS = NO;//把限制打开
    self.isSpeedCacheSmall = NO;//把限制打开
    self.isReturnAdd = NO;//可以返回地址
    
    [self.timer_Report invalidate];//清除定时器,因为定时器会去检查是否需要下载接口
    self.timer_Report = nil;
    
    
//    [self.player pause];
//    [[VCVideoPlayerManager PlayManager] pause];
//    [[VCVideoPlayerManager PlayManager] stop];
    
    
    [self requestVideoListWithTime:currentPlaybackTime  isSwitchTime:YES];
}

/**下载ID*/
-(void)downloadVideoWithId:(NSString *)linkId{
    if (self.resourceID) {
        return;
    }
    
    [self endDownload];//更新链接
    [self openServer];
    self.array_accelerate = [NSMutableArray array];
    self.resourceID = linkId;
    self.seekVod = 0;
    self.nextStartSec = 0;
    /**获取列表*/
    __VCWeakSelf
    VCInformationMoudle *moudle = [[VCInformationMoudle alloc] init];
    
    if ([VCInformationTool getKeyDict]) {
        [self requestVideoListWithTime:self.nextStartSec isSwitchTime:YES];
    }else{
        [moudle getKeyWithsucceed:^(id data) {
            [weakSelf requestVideoListWithTime:weakSelf.nextStartSec isSwitchTime:YES];
        } fail:^(NSError *error) {
            VCNSLog(@"error = %@",error);
        }];
    }
    /**开启服务器*/
}

/**请求ts列表数据
 *isSwitchTime 是否在切换时间
 */
-(void)requestVideoListWithTime:(NSInteger)time isSwitchTime:(BOOL)isSwitchTime{
    VCNSLog(@"请求列表的起始时间 %ld",time);
    __VCWeakSelf
    VCInformationMoudle *moudle = [[VCInformationMoudle alloc] init];
    [moudle getVideoListWithLinkId:self.resourceID seekVod:time isStart:YES succeed:^(id data) {
        
        if (isSwitchTime) {
            weakSelf.downloadNum = [data[@"seq"] intValue];
            [VCInformationTool setVC_sequence:weakSelf.downloadNum];//清除序列号
        }
       
        
        weakSelf.isRequestTsList = NO;
        NSLog(@" %@",data);
        NSArray *fileList = data[@"fileList"];
        if (fileList != nil && fileList.count>0) {
            weakSelf.nextStartSec = [data[@"firstSec"] floatValue];
            for (int i = 0; i < fileList.count -1 ; i++) {
                weakSelf.nextStartSec += [[fileList[i] objectForKey:@"duration"] floatValue]*MillisecondsRatio;
            }
        }
        
        weakSelf.dict = [VCInformationTool appendTsListWithSource:weakSelf.dict addList:data];
        [VCInformationTool saveFileDict:weakSelf.dict];
        weakSelf.needCacheTime = [weakSelf.dict[@"preSec"] intValue] * MillisecondsRatio;
        
        /**开始上报数据定时器*/
        [weakSelf timer_Report];
        
        if (time == 0) {//重新开始的,创建ts下载器和和返回地址
            [weakSelf createTsDownload];
            [weakSelf createPath];
//            [weakSelf returnAddress];//返回播放地址
        }
        
    } fail:^(NSError *error) {
        weakSelf.isRequestTsList = NO;
        VCNSLog(@"error = %@",error);
    }];
}

/**加速接口
 *index 要下载片段的索引
 *isSpeed 是否要加速,(udp正在下载,可是未下载完成,切换cdn)
 */
-(void)startAccelerateWithIndex:(NSUInteger)index isSpeed:(BOOL)isSpeed{
    NSArray *tsFileList = [self.dict objectForKey:@"fileList"];
    NSInteger listIndex = index - [[self.dict objectForKey:@"seq"] integerValue];
    if (listIndex < tsFileList.count) {
        __VCWeakSelf
        NSDictionary *dict = tsFileList[listIndex];
        
//        NSString *path = [kVideoSavePath stringByAppendingPathComponent:[NSString stringWithFormat:@"%@.%lu.ts",[dict objectForKey:@"fileId"],index]];
        NSString *path = [kVideoSavePath stringByAppendingPathComponent:[NSString stringWithFormat:@"%lu.ts",index]];
        
        VCInformationMoudle *moudle = [[VCInformationMoudle alloc] init];
        NSURLSessionDataTask *task = [moudle getAccelerateWithLinkId:[dict objectForKey:@"fileId"] urlString:[self.dict objectForKey:@"accelerate"] succeed:^(id data) {
            if (isSpeed) {
                weakSelf.isSpeedCacheSmall = NO;
            }else{
                weakSelf.isSpeedDownloadTS = NO;
            }
            
            
            BOOL bSucc = [data writeToFile:path atomically:YES];
            if (bSucc) {
                //播放时长
                weakSelf.alreadyDownloadedTime += [[dict objectForKey:@"duration"] floatValue];
                weakSelf.accelSize += [[dict objectForKey:@"fileSize"] unsignedIntegerValue];
                weakSelf.vcSize += [[dict objectForKey:@"fileSize"] unsignedIntegerValue];
                VCNSLog(@"加速接口 第一个ts数据保存成功%@",path);
                [VCInformationTool saveTSFileWithTsName:path isReset:NO tsNum:0];//保存当前可以观看的ts
//                [weakSelf bitMapAdjustWithAcceptIndex:index];//记录那些事下载完毕的
                
                [weakSelf tsDownloadCompleteWithIndex:index model:1 downloadTs:nil];//ts下载完成回调
            }
        } fail:^(NSError *error) {
            if (isSpeed) {
                weakSelf.isSpeedCacheSmall = NO;
            }else{
                weakSelf.isSpeedDownloadTS = NO;
            }
            VCNSLog(@"error = %@",error);
            NSDictionary *dic = error.userInfo;
            if (![[dic objectForKey:@"NSLocalizedDescription"] isEqualToString:@"cancelled"]) {
                VCNSLog(@"来了这里,就是不是取消的下载错误");
                [weakSelf.array_tsSerial addObject:@(index)];//添加到失败的ts列表中
                [weakSelf tsDownloadCompleteWithIndex:index model:2 downloadTs:nil];//ts下载完成回调
            }
            
        }];
        
        [self.array_accelerate addObject:task];
    }

}
/**停止
 *playTime 播放的时长
 */
-(void)stopDownload{
    if (self.resourceID) {
        VCInformationMoudle *moudle = [[VCInformationMoudle alloc] init];
        [moudle getReportWithResourceID:self.resourceID playTime:self.playTimer accelSize:self.accelSize vcSize:self.vcSize vc:self.array_vc succeed:^(id data) {
            VCNSLog(@"流量上报完毕");
        } fail:^(NSError *error) {
            VCNSLog(@"error = %@",error);
        }];
    }
    [self endDownload];
}
/**停止*/
-(void)endDownload{
    /**停止服务器*/
    [self.httpServer stop];
    self.httpServer = nil;
    /**清除上报内容*/
    [self.array_vc removeAllObjects];
    self.array_vc = nil;
    self.accelSize = 0;
    self.vcSize = 0;
    self.resourceID = nil;
    self.playTimer = 0;
    
    
    /**调试页面的数据*/
    [self removeDebug];
    self.vcSize = 0;
    [self.array_vc removeAllObjects];
    self.array_vc = 0;
    self.isSuspend = NO;
    self.alreadyDownloadedTime = 0;
    self.alreadyPlayTime = 0;
    self.noCatonTime = 0;
    self.catonNum = 0;
    self.catonTimer = 0;
    
    /**定时器清除*/
    [self.timer_Report invalidate];
    self.timer_Report = nil;
    [self.timer_debug invalidate];
    self.timer_debug = nil;
    
    self.downloadNum = 0;
    self.dict = nil;
    self.PlayNnm = 0;
    self.isReturnAdd = NO;//可以返回地址
    self.isSpeedDownloadTS = NO;//把限制打开
    self.isSpeedCacheSmall = NO;//把限制打开
    [VCInformationTool setPlayerIsRestart:NO];
    [VCInformationTool setVideoIsLastTs:NO];
    
    /**告诉ts下载器也要停止*/
    [self.array_Ts makeObjectsPerformSelector:@selector(closeDownload)];
    [self.array_Ts removeAllObjects];
    [self.array_tsSerial removeAllObjects];
    [self.array_accelerate makeObjectsPerformSelector:@selector(cancel)];
    [self.array_accelerate removeAllObjects];
    self.array_accelerate = nil;
    [VCInformationTool setVC_sequence:0];//ts重新开始
    
    [VCInformationTool saveTSFileWithTsName:nil isReset:YES tsNum:0];
    [VCInformationTool deleteFileWithPath:kVideoSavePath];//清除缓存
}
/**启动调试页面
 *ducation 视频总时长
 */
/**启动调试页面
 *number 卡顿次数
 */
-(void)startDeBugViewCaton{
    if (self.debugView == nil) {
        VCDebugView *view = [[VCDebugView alloc] initWithFrame:[UIScreen mainScreen].bounds];
        [[UIApplication sharedApplication].keyWindow addSubview:view];
        for (int i = 0; i < self.array_Ts.count; i++) {
            VCDownloadTs *ts = self.array_Ts[i];
            UILabel *label_ts = view.array_Ts[i];
            UILabel *label_info = view.array_ipInfo[i];
            label_ts.hidden = ts.isFree;
            label_info.hidden = ts.isFree;
        }
        self.debugView = view;
        [self.timer_debug invalidate];
        self.timer_debug = nil;
        __VCWeakSelf
        self.timer_debug = [NSTimer scheduledTimerWithTimeInterval:DEBUG_TIME repeats:YES block:^(NSTimer * _Nonnull timer) {
            [[NSNotificationCenter defaultCenter] postNotificationName:VCDownloadDebugNotification object:nil];
            
            [view alreadyDownloadedTime:weakSelf.alreadyDownloadedTime alreadyPlayTime:weakSelf.alreadyPlayTime noCatonTime:weakSelf.noCatonTime catonTimer:weakSelf.catonTimer catonNum:weakSelf.catonNum];
            if (weakSelf.isSuspend) {//正在暂停
                weakSelf.catonTimer += DEBUG_TIME;
            }else{
                weakSelf.noCatonTime += DEBUG_TIME;
            }
            
        }];
        [[NSRunLoop mainRunLoop] addTimer:self.timer_debug forMode:NSRunLoopCommonModes];
        
        
    }

}

/**去除调试页面*/
-(void)removeDebug{
    [self.debugView removeFromSuperview];
    self.debugView = nil;
}
/**播放器暂停播放*/
-(void)playerSuspendPlay{
    self.catonNum++;//卡顿一次加一次
    self.isSuspend = YES;//正在暂停
    self.noCatonTime = 0;//清除持续时长
}
/**播放器开始播放*/
-(void)playerStartPlay{
    self.isSuspend = NO;//已经开始播放
}

/**开启本地服务器*/
- (void)openServer {
    if (self.httpServer) {
        return;
    }
    [DDLog addLogger:[DDTTYLogger sharedInstance]];
    
    self.httpServer=[[HTTPServer alloc]init];
    [self.httpServer setType:@"_http._tcp."];
    self.serverProt = 12345;
    [self.httpServer setPort:self.serverProt];
    NSString *pathPrefix = [NSSearchPathForDirectoriesInDomains(NSDocumentDirectory,NSUserDomainMask,YES) objectAtIndex:0];
    NSString *webPath = [pathPrefix stringByAppendingPathComponent:@"Downloads"];
    
    [self.httpServer setDocumentRoot:webPath];
    self.httpServer.connectionClass = [VCDownloadHTTPConnection class];
    
    VCNSLog(@"服务器路径：%@", webPath);
    NSError *error;
    if ([self.httpServer start:&error]) {
        VCNSLog(@"开启HTTP服务器 端口:%hu",[self.httpServer listeningPort]);
        self.urlString = [NSString stringWithFormat:@"http://127.0.0.1:%ld/movie1/movie.m3u8",self.serverProt];
    }
    else{
        VCNSLog(@"服务器启动失败错误为:%@",error);
        self.serverProt++;
        [self.httpServer setPort:self.serverProt];
        [self.httpServer start:&error];
    }
}


/**创建ts下载器*/
-(void)createTsDownload{
    
    [self createTsNewDownload];
    
    [self selectDownloadModelWithIndex:self.downloadNum];
}
/**去下载当前的ts
 会判断当前使用CDN还是udp下载
 */
-(void)selectDownloadModelWithIndex:(NSInteger)index{
    
    [self againCheckFailedTSWithDownloadTs:nil];//检查失败的ts
    
    NSTimeInterval playerBuffering = 0;
    if ([self.delegate respondsToSelector:@selector(playerBufferTimeWithdownload:)]) {
        playerBuffering = [self.delegate playerBufferTimeWithdownload:self];
    }
    VCNSLog(@"totalCacheTime = %lf index = %ld",self.totalCacheTime,index);
    
    if ([VCInformationTool checkTSFileIsHaveWithTsNum:index] && self.totalCacheTime + playerBuffering < self.needCacheTime) {//检查本地存在
        self.downloadNum++;
        [self tsDownloadCompleteWithIndex:index model:1 downloadTs:nil];//ts下载完成回调
        return;
    }
    
    if (self.totalCacheTime +  playerBuffering < self.changeCDNPoint || index < 3) {//缓存量低于cdn的临界点,切换cdn下载
//    if (self.totalCacheTime < self.needCacheTime){//缓存量低于需要的缓存时间,使用udp添加
        
        if (!self.isSpeedDownloadTS && !self.isSpeedCacheSmall) {//没有加速下载的
            self.isSpeedDownloadTS = YES;
            self.downloadNum++;
            VCNSLog(@"来了加速接口 %li",index);
            [self startAccelerateWithIndex:index isSpeed:NO];/**使用cdn加速*/
        }
    }
    else if (self.totalCacheTime + playerBuffering < self.needCacheTime){//缓存量低于需要的缓存时间,使用udp添加
        for (VCDownloadTs *ts in self.array_Ts) {
            if (ts.isFree) {//看这些时间  来过这里吗
                VCNSLog(@"来了udp接口 %i",self.downloadNum);
                /**判断一下有没有配置端口*/
                [self downloadWithTSNnm:(int)self.downloadNum ts:ts];
                self.downloadNum++;
            }
        }
    }
}

/**ts下载完成回调
 *model 0默认udp下载成功 1cdn下载成功 2下载失败
 *downloadTs model==0的时候要传
 */
#warning 还有失败的情况
-(void)tsDownloadCompleteWithIndex:(NSInteger)index model:(int)model downloadTs:(VCDownloadTs *)downloadTs{
    
    
    [self againCheckFailedTSWithDownloadTs:downloadTs];//检查失败的ts
    
    //清除加速task
    [self.array_accelerate removeAllObjects];
    if (model == 2)return;
    
    NSInteger listIndex = index - [[self.dict objectForKey:@"seq"] integerValue];
    
    //添加缓存时间
    NSArray *array = self.dict[@"fileList"];
    if (listIndex < array.count) {
        NSDictionary *dict = array[listIndex];
        self.totalCacheTime += [dict[@"duration"] floatValue] * MillisecondsRatio;
        VCNSLog(@"添加的缓存时间 缓存的时间%lf,请求之后减去%@ index = %i",self.totalCacheTime,dict[@"duration"],(int)index);
        
        self.seekVod += ([[dict objectForKey:@"duration"] floatValue] * MillisecondsRatio);
        VCNSLog(@"看一下时间seekvod = %ld duration=%lf  duration = %@",self.seekVod,[[dict objectForKey:@"duration"] floatValue] * MillisecondsRatio,[dict objectForKey:@"duration"]);
    }
    
    if (self.dict) {
        //重新检查是否需要继续下载
        [self selectDownloadModelWithIndex:self.downloadNum];
    }
    
    
    if (listIndex >= array.count - 10 && !self.isRequestTsList) {//请求新的列表
        self.isRequestTsList = YES;
        [self requestVideoListWithTime:self.nextStartSec isSwitchTime:NO];//重新请求
    }
    
    NSInteger fileCnt = [[self.dict objectForKey:@"fileCnt"] integerValue];
    if (!self.isReturnAdd && (self.totalCacheTime > 10000 || self.downloadNum > fileCnt)) {//当下载完成第一个的时候,可以返回m3u8的地址
        if ([VCInformationTool getPlayerIsRestart]) {//重新启动
            if ([VCInformationTool checkTSFileIsHaveWithTsNum:[VCInformationTool getVC_sequence]]) {
                [self returnAddress];
            }else{//换加速接口
                if ([VCInformationTool checkTSFileIsHaveWithTsNum:[VCInformationTool getVC_sequence]]) {
                    [self DownloadPlayerTs:[[NSNotification alloc] initWithName:VCDownloadSendDownloadNotification object:nil userInfo:@{PLAY_NUM_TS:@([VCInformationTool getVC_sequence])}]];
                }
            }
            
        }else{//第一次启动
            [self returnAddress];
        }
        
    }
    
}
/**重新下载失败的ts
 *downloadTs 可以进行下载的udp下载器
 */
-(void)againCheckFailedTSWithDownloadTs:(VCDownloadTs *)downloadTs{
    for (NSNumber *tsNum in self.array_tsSerial) {
        
        if (!self.isSpeedDownloadTS) {//没有使用cdn
            VCNSLog(@"加速接口 在失败这里加载 num = %@",tsNum);
            self.isSpeedDownloadTS = YES;
            [self startAccelerateWithIndex:[tsNum intValue] isSpeed:NO];/**使用cdn加速*/
            [self.array_tsSerial removeObject:tsNum];
            break;
        }else if(downloadTs.isFree){//使用udp下载
            VCNSLog(@"udp 在失败这里加载 dit = %@",tsNum);
            [self downloadWithTSNnm:[tsNum intValue] ts:downloadTs];
            [self.array_tsSerial removeObject:tsNum];
            break;
        }
    }
}

/**创建下载器*/
-(void)createTsNewDownload{
    [self.array_tsHost removeAllObjects];
    
    NSArray *array = [self.dict objectForKey:@"hostList"];
    self.hostCount = array.count;
    for (int i = 0; i<array.count && i < 3; i++) {
        VCDownloadTs *ts = [[VCDownloadTs alloc] init];
        [self.array_Ts addObject:ts];
        
        ts.delegate = self;
        NSString *host = [[array objectAtIndex:i] objectForKey:@"host"];
        NSRange range = [host localizedStandardRangeOfString:@":"];
        ts.hostAndPort = host;
        ts.host = [host substringToIndex:range.location];
        ts.clientProt = i + 9555;
        ts.clientTSProt = i + 19999;
        ts.prot = [[host substringFromIndex:range.location+1] integerValue];
        VCNSLog(@"host = %@ %@",host,ts);
        //        [self downloadWithTSNnm:self.downloadNum++ ts:ts];
    }
}

/**检查没有下载完毕的*/
-(void)checkDownloadFial{
    for (NSNumber *tsNum in self.array_tsSerial) {
        
        for (VCDownloadTs *newts in self.array_Ts) {
            if (newts.isFree) {
                /**判断一下有没有配置端口*/
                VCNSLog(@"判断一下有没有配置端口");
                [self downloadWithTSNnm:[tsNum intValue] ts:newts];
                [self.array_tsSerial removeObject:tsNum];
                break;
            }
        }
    }
    for (VCDownloadTs *ts in self.array_Ts) {
        if (ts.isFree) {
            /**判断一下有没有配置端口*/
            if (self.downloadNum > self.PlayNnm+3) {//缓存多三个了
                break;
            }else{
                VCNSLog(@"判断一下有没有配置端口2");
                [self downloadWithTSNnm:self.downloadNum++ ts:ts];
            }
        }
    }
    
}

/**开始加载第几个ts*/
-(void)downloadWithTSNnm:(int)num ts:(VCDownloadTs *)ts{
    
    NSInteger listIndex = num - [[self.dict objectForKey:@"seq"] intValue];
    NSArray *fileList = [self.dict objectForKey:@"fileList"];
    if (listIndex < fileList.count) {
        ts.dict_file = [fileList objectAtIndex:listIndex];
        ts.currentTsNum = num;//记录当前ts位置
        VCNSLog(@"%@ 看看你的dic == %@",ts,ts.dict_file);

        /**开始下载*/
        [ts startDownload];
        [self.debugView startShowWithIndex:[self.array_Ts indexOfObject:ts]];
    }

}


/**返回地址*/
-(void)returnAddress{
    self.isReturnAdd = YES;
    VCNSLog(@"来到这里看地址吗???");
    [VCInformationTool setPlayerChangeTime:NO];
    __VCWeakSelf
    dispatch_async(dispatch_get_main_queue(), ^{
        if ([weakSelf.delegate respondsToSelector:@selector(download:url:)]) {
            [weakSelf.delegate download:weakSelf url:[NSString stringWithFormat:@"http://127.0.0.1:%ld/movie1/movie.m3u8",weakSelf.serverProt]];
        }
    });
    
    
}


/**创建路径*/
-(void)createPath{
    NSFileManager *fm = [NSFileManager defaultManager];
    NSString *saveTo = [[[NSSearchPathForDirectoriesInDomains(NSDocumentDirectory,NSUserDomainMask,YES) objectAtIndex:0] stringByAppendingPathComponent:@"Downloads"] stringByAppendingPathComponent:@"movie1"];
    if (![fm fileExistsAtPath:saveTo isDirectory:nil]) {
        //不存在这个链接
        BOOL isS = [fm createDirectoryAtPath:saveTo withIntermediateDirectories:YES attributes:nil error:nil];
        if (isS) {
            VCNSLog(@"创建目录成功");
        } else {
            VCNSLog(@"创建目录失败");
        }
    }

}


#pragma mark - 通知
/**回到前台*/
-(void)willEnterForeground:(NSNotification *)noti{
    if (self.isScreenOff || ![self.httpServer isRunning]) {
        self.isScreenOff = NO;
        VCNSLog(@"回到了前台");
        [self.httpServer stop];
        self.httpServer = nil;
        [self openServer];
//
//        [self performSelector:@selector(sssssssss) withObject:nil afterDelay:1.5];

    }
    
//    if (![self.httpServer isRunning]) {
//        VCNSLog(@"回到了前台");
//        [self.httpServer stop];
//        self.httpServer = nil;
//        [self openServer];
//    }
//    VCNSLog(@"回到了前台");
//    [self.httpServer stop];
//    self.httpServer = nil;
//    [self openServer];
}
/**进入后台*/
-(void)willEnterBackground:(NSNotification *)noti{
//    if (self.isScreenOff) {
//        self.isScreenOff = NO;
//        VCNSLog(@"回到了前台");
//        [self.httpServer stop];
//        self.httpServer = nil;
//        [self openServer];
//
//        [self performSelector:@selector(sssssssss) withObject:nil afterDelay:1.5];
//
//    }
}

-(void)sssssssss{
    __VCWeakSelf
    dispatch_async(dispatch_get_main_queue(), ^{
        
        if ([weakSelf.delegate respondsToSelector:@selector(download:player:)]) {
//            [weakSelf.delegate download:weakSelf player:weakSelf.player];
            
            [weakSelf.delegate download:weakSelf url:[NSString stringWithFormat:@"http://127.0.0.1:%ld/movie1/movie.m3u8",weakSelf.serverProt]];
            
        }
    });
}

/**打通道失败,更换接口*/
-(void)changeNewHostDownload:(NSNotification *)noti{
    
    VCDownloadTs *ts = [noti.userInfo objectForKey:VC_TS];
    
    VCNSLog(@"打通道失败,index = %ld  dic = %@",ts.currentTsNum,ts.dict_file);
    
    NSArray *array = [self.dict objectForKey:@"hostList"];
    
    BOOL isDistribution = NO;
    for (NSDictionary *dict_host in array) {
        isDistribution = NO;
        for (VCDownloadTs *downloadTS in self.array_Ts) {//检查dict_host是否被使用的
            if ([downloadTS.hostAndPort isEqualToString:[dict_host objectForKey:@"host"]]) {
                isDistribution = YES;
                break;
            }
        }
        if (!isDistribution) {//检查是否之前用过了
            for (NSString *host in self.array_tsHost) {//检查是否废弃的host
                if ([host isEqualToString:[dict_host objectForKey:@"host"]]) {
                    isDistribution = YES;
                    break;
                }
            }
        }
        
        if (!isDistribution) {//没有被分配
            
            ts.delegate = self;
            NSString *host = [dict_host objectForKey:@"host"];
            NSRange range = [host localizedStandardRangeOfString:@":"];
            ts.host = [host substringToIndex:range.location];
            ts.clientProt = ts.clientProt + 1;
            ts.clientTSProt = ts.clientTSProt + 1;
            ts.prot = [[host substringFromIndex:range.location+1] integerValue];
            /**开始下载*/
            [ts startDownload];
            [self.debugView startShowWithIndex:[self.array_Ts indexOfObject:ts]];
            break;
        }
    }
    
    //没办法更换接口,那就接口不可以,吧当前下载的任务给别人
    if (isDistribution) {//没有可用的host
        [self.debugView completeHiddenWithIndex:[self.array_Ts indexOfObject:ts]];
        [ts closeDownload];
        [self.array_Ts removeObject:ts];//因为host不可以,而且没有可用的替代,所以这个ts下载器丢弃
        
        [self.array_tsHost addObject:ts.hostAndPort];
        
        if (self.array_Ts.count < 2 && (self.networkReachabilityStatus == AFNetworkReachabilityStatusReachableViaWiFi || self.networkReachabilityStatus == AFNetworkReachabilityStatusReachableViaWWAN)) {//没有了,重新创建
            
            for (int i = 0; i<self.array_tsHost.count && i < 2; i++) {
                VCDownloadTs *ts = [[VCDownloadTs alloc] init];
                [self.array_Ts addObject:ts];
                
                ts.delegate = self;
                NSString *host = [self.array_tsHost objectAtIndex:i];
                NSRange range = [host localizedStandardRangeOfString:@":"];
                ts.hostAndPort = host;
                ts.host = [host substringToIndex:range.location];
                ts.clientProt = i + 9555;
                ts.clientTSProt = i + 19999;
                ts.prot = [[host substringFromIndex:range.location+1] integerValue];
//                VCNSLog(@"host = %@ %@",host,ts);
            }
            
            if (self.array_tsHost.count > 1) {
                NSIndexSet *set = [[NSIndexSet alloc] initWithIndexesInRange:NSMakeRange(0, 2)];
                [self.array_tsHost removeObjectsAtIndexes:set];
            }else if (self.array_tsHost.count == 1){
                [self.array_tsHost removeObjectAtIndex:0];
            }
            
        }
        
        BOOL isFree = NO;
        for (VCDownloadTs *newts in self.array_Ts) {
            if (newts.isFree) {
                isFree = YES;
                /**判断一下有没有配置端口*/
                VCNSLog(@"打通道失败了");
                [self downloadWithTSNnm:(int)ts.currentTsNum ts:newts];
                break;
            }
        }
        if (!isFree) {
            BOOL isSave = NO;//是否保存过了
            for (NSNumber *num in self.array_tsSerial) {
                if ([num integerValue] == ts.currentTsNum) {
                    isSave = YES;
                    break;
                }
            }
            if (!isSave) {
                [self.array_tsSerial addObject:@(ts.currentTsNum)];//添加上去.他要换ts
            }
        }
    }
    
    
    
}
/**播放器正在请求的ts*/
-(void)playGetTs:(NSNotification *)noti{
    __VCWeakSelf
    dispatch_async(dispatch_get_main_queue(), ^{
        int playNum = [[noti.userInfo objectForKey:PLAY_NUM_TS] intValue];
        
        NSArray *fileList = weakSelf.dict[@"fileList"];
        
        [weakSelf selectDownloadModelWithIndex:weakSelf.downloadNum];
        NSInteger listIndex = playNum - [[self.dict objectForKey:@"seq"] integerValue];
        if (listIndex < fileList.count) {
            NSDictionary *dict = fileList[listIndex];
            
            weakSelf.totalCacheTime -= [dict[@"duration"] floatValue] * MillisecondsRatio;
            VCNSLog(@"减去的缓存时间 缓存的时间%lf,请求之后减去%@ index = %i",weakSelf.totalCacheTime,dict[@"duration"],playNum);
        }
    });
}

/**收到播放器请求下载ts*/
-(void)DownloadPlayerTs:(NSNotification *)noti{
    __VCWeakSelf
    dispatch_async(dispatch_get_main_queue(), ^{//
        int playNum = [[noti.userInfo objectForKey:PLAY_NUM_TS] intValue];
        
        NSTimeInterval playerBuffering = 0;
        if ([weakSelf.delegate respondsToSelector:@selector(playerBufferTimeWithdownload:)]) {
            playerBuffering = [weakSelf.delegate playerBufferTimeWithdownload:self];
        }
        
        NSTimeInterval changeCDNPoint = weakSelf.changeCDNPoint < 15000 ? weakSelf.changeCDNPoint + 5000 : weakSelf.changeCDNPoint;
        
        VCDownloadTs *cureenDownloadTs;
        for (VCDownloadTs *downloadTs in weakSelf.array_Ts) {
            if (downloadTs.currentTsNum == playNum) {
                cureenDownloadTs = downloadTs;
                break;
            }
        }
        VCNSLog(@"看看这些时间 totalCacheTime = %lf playerBuffering = %lf  百分比 = %i num = %i",weakSelf.totalCacheTime,playerBuffering,[cureenDownloadTs getTsDownloadProgress],playNum);
        if (playerBuffering < changeCDNPoint) {//缓存量低于cdn的临界点,切换cdn下载
            if (!weakSelf.isSpeedCacheSmall && cureenDownloadTs != nil && [cureenDownloadTs getTsDownloadProgress]<40 ) {
                NSArray *array = weakSelf.dict[@"fileList"];
                NSInteger listIndex = playNum - [[self.dict objectForKey:@"seq"] integerValue];
                VCNSLog(@"看看这些时间  来过这里吗?? num = %i  dic = %@",playNum,array[listIndex]);
                weakSelf.isSpeedCacheSmall = YES;
                [weakSelf startAccelerateWithIndex:playNum isSpeed:YES];/**使用cdn加速*/
                
                [cureenDownloadTs stopDownloadTs];//停止之前的下载
            }
        }
    });

}

#pragma mark - VCDownloadTsDelegate
/**数据下载完毕回调
 *completeWithDataModel :数据
 */
-(void)download:(VCDownloadTs *)downloadTs completeWithDataModel:(VCTsDataModel *)model{
    [self.debugView completeHiddenWithIndex:[self.array_Ts indexOfObject:downloadTs]];
    NSString *path_root = kVideoSavePath;
    
//    NSString *path = [path_root stringByAppendingPathComponent:[NSString stringWithFormat:@"%@.%lu.ts",[downloadTs.dict_file objectForKey:@"fileId"],downloadTs.currentTsNum]];
    NSString *path = [path_root stringByAppendingPathComponent:[NSString stringWithFormat:@"%lu.ts",downloadTs.currentTsNum]];
    
    BOOL bSucc = [model.data writeToFile:path atomically:YES];
    
    if (bSucc) {
        //播放时长
        self.alreadyDownloadedTime += [[downloadTs.dict_file objectForKey:@"duration"] floatValue];
//        downloadTs.isFree = YES;//空闲了
        //成功
        VCNSLog(@"%@ udp 第一个ts数据保存成功%@",downloadTs,[downloadTs.dict_file objectForKey:@"fileId"]);
        
        
        
        [self recordFlowWiftFileDict:downloadTs];//记录有效流量
        
//        [self bitMapAdjustWithAcceptIndex:downloadTs.currentTsNum];//记录那些事下载完毕的
        [VCInformationTool saveTSFileWithTsName:path isReset:NO tsNum:[self.array_Ts indexOfObject:downloadTs]+1];//保存当前可以观看的ts
        
        
        if (self.PlayNnm>0) {//删除之前的
            NSArray *fileList = [self.dict objectForKey:@"fileList"];
            if (self.PlayNnm - 1 < fileList.count) {
                NSDictionary *dict_file = [fileList objectAtIndex:self.PlayNnm - 1];
                NSString *path_delegeta = [path_root stringByAppendingPathComponent:[NSString stringWithFormat:@"%@.%lu.ts",[dict_file objectForKey:@"fileId"],downloadTs.currentTsNum]];
                [VCInformationTool deleteFileWithPath:path_delegeta];
            }
            
        }
        
        [self tsDownloadCompleteWithIndex:downloadTs.currentTsNum model:0 downloadTs:downloadTs];//ts下载完成回调
        
//        [self checkNeedAssistDownloadWitg:downloadTs isRegularlyCheck:NO];//检查是否要帮忙和没有需要帮忙就继续往下下载
    } else {
        [model.data writeToFile:path atomically:YES];//继续写入
        //失败
        VCNSLog(@"第一个ts数据保存失败=====");
    }
    
    
}

/**辅助下载完毕回调
 *auxiliaryCompleteWithDataModel :数据
 */
-(void)download:(VCDownloadTs *)downloadTs auxiliaryCompleteWithDataModel:(VCTsDataModel *)model{
    
    [self.debugView completeHiddenWithIndex:[self.array_Ts indexOfObject:downloadTs]];
    AuxiliaryModel *auxiliaryModelOne;
    for (AuxiliaryModel *auxiliary in self.array_auxiliary) {
        if (auxiliary.tsNum == downloadTs.currentTsNum) {
            auxiliaryModelOne = auxiliary;
        }
    }
    if (auxiliaryModelOne) {//之前宜家完成一部分 拼装
        
//        auxiliaryModelOne.data = [NSMutableData dataWithLength:[[downloadTs.dict_file objectForKey:@"fileSize"] unsignedIntValue]];
        
        [self appendTsDataWith:(int)downloadTs.startPoint length:(downloadTs.endPoint - downloadTs.startPoint +1 ) * 1400 data:model.data appenData:auxiliaryModelOne.data];
        
        auxiliaryModelOne.totalAppendLength = downloadTs.endPoint - downloadTs.startPoint + 1 + auxiliaryModelOne.totalAppendLength;
        
        if (auxiliaryModelOne.totalAppendLength == auxiliaryModelOne.totalLength + 1) {//拼接完毕
            //恢复最正确的长度
            auxiliaryModelOne.data = [NSMutableData dataWithBytes:auxiliaryModelOne.data.bytes length:[[downloadTs.dict_file objectForKey:@"fileSize"] unsignedIntegerValue]];
            
            [self recordFlowWiftFileDict:downloadTs];
            //播放时长
            self.alreadyDownloadedTime += [[downloadTs.dict_file objectForKey:@"duration"] floatValue];
            //保存数据
            NSString *path_root = kVideoSavePath;
            
//            NSString *path = [path_root stringByAppendingPathComponent:[NSString stringWithFormat:@"%@.%lu.ts",[downloadTs.dict_file objectForKey:@"fileId"],downloadTs.currentTsNum]];
            NSString *path = [path_root stringByAppendingPathComponent:[NSString stringWithFormat:@"%lu.ts",downloadTs.currentTsNum]];
            BOOL bSucc = [auxiliaryModelOne.data writeToFile:path atomically:YES];
            
            if (bSucc) {
                VCNSLog(@"%@ 辅助 udp 第一个ts数据保存成功(在辅助)%@",downloadTs,[downloadTs.dict_file objectForKey:@"fileId"]);
                [self tsDownloadCompleteWithIndex:downloadTs.currentTsNum model:0 downloadTs:downloadTs];//ts下载完成回调
            }
            
            
            [VCInformationTool saveTSFileWithTsName:path isReset:NO tsNum:[self.array_Ts indexOfObject:downloadTs]+1];//保存当前可以观看的ts
            //删除缓存
            [self.array_auxiliary removeObject:auxiliaryModelOne];
        }else{
            VCNSLog(@"%@ 第二个片段好了 (辅助)%@",downloadTs,[downloadTs.dict_file objectForKey:@"fileId"]);
        }
        
    }else{//第一次进来
        VCNSLog(@"%@ 第一个片段好了 (辅助)%@",downloadTs,[downloadTs.dict_file objectForKey:@"fileId"]);
        
        auxiliaryModelOne = [[AuxiliaryModel alloc] init];
        auxiliaryModelOne.data = [NSMutableData dataWithLength:[[downloadTs.dict_file objectForKey:@"fileSize"] unsignedIntegerValue]];
        
        [self appendTsDataWith:(int)downloadTs.startPoint length:(downloadTs.endPoint - downloadTs.startPoint +1 ) * 1400  data:model.data appenData:auxiliaryModelOne.data];
        
        auxiliaryModelOne.tsNum = downloadTs.currentTsNum;
        auxiliaryModelOne.dict_file = downloadTs.dict_file;
        auxiliaryModelOne.totalAppendLength = downloadTs.endPoint - downloadTs.startPoint + 1;
        
        unsigned int size = [[downloadTs.dict_file objectForKey:@"fileSize"] unsignedIntValue];
        auxiliaryModelOne.totalLength = size / PAGE_SIZE;
        if (size % PAGE_SIZE == 0) {
            auxiliaryModelOne.totalLength--;
        }
        [self.array_auxiliary addObject:auxiliaryModelOne];
    }
    
    
    downloadTs.isAuxiliaryDownload = NO;//当前有空的ts下载器帮忙下载
    downloadTs.auxiliaryOrder = 0;
    downloadTs.startPoint = 0;
    downloadTs.endPoint = 0;
//    downloadTs.isFree = YES;
    
    for (AuxiliaryModel *auxiliary in self.array_auxiliary) {
        if (auxiliary.tsNum + 10 < self.PlayNnm) {//超出请求所要的
            [self.array_auxiliary removeObject:auxiliary];
            break;
        }
    }
    
    if ([self checkFailureWithdownload:downloadTs]) return;//存在要重新下载的
    
    [self checkNeedAssistDownloadWitg:downloadTs isRegularlyCheck:NO];//检查是否要帮忙和没有需要帮忙就继续往下下载
}

/**检查是否要帮忙
 *isRegularlyCheck yes定时器检测,当前空闲的ts下载器检查是否要帮忙,不需要理会currentTsNum,No刚刚下载完成一个,检查比自己小的currentTsNum来帮忙
 */
-(void)checkNeedAssistDownloadWitg:(VCDownloadTs *)downloadTs isRegularlyCheck:(BOOL)isRegularlyCheck{
    /**找序列号最前面的ts*/
    NSMutableArray *array_M_last = [NSMutableArray array];//看前面有多少个ts
    for (VCDownloadTs *ts in self.array_Ts) {
        if (!ts.isFree) {
            [array_M_last addObject:ts];
        }
    }

    /**得出一个数组
     *数组为元素为0,当前下载完毕的ts就是最前面的
     *1前面有一个还没有下载完,要帮忙
     *2,前面两个单独在下载,或者前面两个下载同一个ts
     */
    
    if (array_M_last.count == 1) {//1前面有一个还没有下载完,要帮忙
        VCDownloadTs *tsFront = array_M_last[0];
//        VCNSLog(@"%@ 来帮忙啦啦one = %@",downloadTs,[tsFront.dict_file objectForKey:@"fileId"]);
        
        [self setAuxiliaryWithAuxiliary:downloadTs BeAided:tsFront];
        
    }else if(array_M_last.count == 2) {//前面两个没有下载完,或者前面第二个下载完,在帮第一个忙,所以也要帮忙
        VCDownloadTs *tsFront = array_M_last[0];
        if (tsFront.auxiliaryOrder > 0) {//前面两个下载同一个ts
            tsFront = tsFront.auxiliaryOrder > [array_M_last[1] auxiliaryOrder]?tsFront:array_M_last[1];
//            VCNSLog(@"%@ 来帮忙啦啦two = %@",downloadTs,[tsFront.dict_file objectForKey:@"fileId"]);
            
            [self setAuxiliaryWithAuxiliary:downloadTs BeAided:tsFront];
            
        }else{//两个单独在下载,去帮第一个
            tsFront = tsFront.currentTsNum < [array_M_last[1] currentTsNum]?tsFront:array_M_last[1];
//            VCNSLog(@"%@ 来帮忙啦啦three = %@",downloadTs,[tsFront.dict_file objectForKey:@"fileId"]);
//            VCNSLog(@"%@ = %lu %@ = %lu",tsFront,tsFront.currentTsNum,array_M_last[1],[array_M_last[1] currentTsNum]);
            [self setAuxiliaryWithAuxiliary:downloadTs BeAided:tsFront];
        }
        
    }else{//是最前面那个,继续下载下一个
        
        if (self.downloadNum <= self.PlayNnm+3) {//判断当前下载到量比播放量还少
            VCNSLog(@"检查是否要帮忙");
            [self downloadWithTSNnm:self.downloadNum++ ts:downloadTs];
        }
    }
}


/**调试界面,返回当前完成第几个包
 *completeIndex :第几个包
 */
/**调试界面,返回当前完成第几个包
 *completeIndex :第几个包
 */
-(void)download:(VCDownloadTs *)downloadTs bitmap:(NSData *)bitmap{
    if (self.debugView && downloadTs.currentTsNum == self.PlayNnm) {//存在调试界面,并且是当前要下载的ts
        [self.debugView setPageColorWithIndex:[self.array_Ts indexOfObject:downloadTs]+1 startPoint:downloadTs.startPoint bitmap:bitmap];
    }
}
/**调试界面,返回当前完成第几个包
 *completeIndex :第几个包
 */
-(void)download:(VCDownloadTs *)downloadTs completeIndex:(NSUInteger)completeIndex{
    if (self.debugView && downloadTs.currentTsNum == self.PlayNnm) {//存在调试界面,并且是当前要下载的ts
        [self.debugView setYellowPageColorWithIndex:[self.array_Ts indexOfObject:downloadTs]+1 indePage:completeIndex];
    }
}
/**调试界面,返回当前完成第几个包
 *downloadTs :ts下载器
 *bitMap :当前下载量
 */
-(void)download:(VCDownloadTs *)downloadTs
         bitMap:(NSData *)bitMap{
    NSTimeInterval timer = [[NSDate date] timeIntervalSince1970] - downloadTs.timer;
    [self.debugView setTsName:[downloadTs.dict_file objectForKey:@"fileId"]
                     fileSize:bitMap.length*1400*8
                       bitMap:bitMap
                        timer:timer
                      tsIndex:[self.array_Ts indexOfObject:downloadTs]];
}
/**调试界面,返回当前完成第几个包
 *downloadTs :ts下载器
 *instantaneousSpeed:瞬时速度
 *downloadTotal:下载总量
 *tunnelId
 *state 当前处于的状态 0打通道Tunnel 1订阅subcribe 2传输数据data状态
 */
-(void)download:(VCDownloadTs *)downloadTs
instantaneousSpeed:(NSUInteger)instantaneousSpeed
  downloadTotal:(NSUInteger)downloadTotal
       tunnelId:(NSInteger)tunnelId
          state:(int)state{
    [self.debugView settsIndex:[self.array_Ts indexOfObject:downloadTs]
                          Tsip:downloadTs.hostAndPort
            instantaneousSpeed:instantaneousSpeed
                 downloadTotal:downloadTotal
                      tunnelId:tunnelId
                         state:state];
}
/**检查下载失败列表,要重新下载就返回yes 不要就NO*/
-(BOOL)checkFailureWithdownload:(VCDownloadTs *)downloadTs {
    if (self.array_tsSerial.count>0) {//有存在要更换的下载器的ts
        int tsNum = [self.array_tsSerial[0] intValue];
        
        if (tsNum<3) {//http请求
            [self startAccelerateWithIndex:tsNum isSpeed:NO];
        }else{
            VCNSLog(@"检查下载失败列表");
            [self downloadWithTSNnm:tsNum ts:downloadTs];
        }
        [self.array_tsSerial removeObjectAtIndex:0];
        
        return YES;
    }
    return NO;
}

/**拼接之前接受的数据*/
-(void)appendTsDataWith:(int)index length:(NSUInteger)length data:(NSData *)data appenData:()totalData{
    [totalData replaceBytesInRange:NSMakeRange(index * PAGE_SIZE, length) withBytes:data.bytes];
}

/**设置辅助下载属性
 *auxiliary 要辅助别人的
 *beAided   被别人辅助的
 */
-(void)setAuxiliaryWithAuxiliary:(VCDownloadTs *)auxiliary BeAided:(VCDownloadTs *)beAided{
    
    
    if ([beAided isNeedAuxiliary]) {//要辅助
        if (beAided.auxiliaryOrder == 0) {//没有被辅助过
            beAided.auxiliaryOrder = 1;//正在被辅助;
            
        }
        
        beAided.isAuxiliaryDownload = YES;//当前有空的ts下载器帮忙下载
        auxiliary.isAuxiliaryDownload = YES;//当前有空的ts下载器帮忙下载
        auxiliary.currentTsNum = beAided.currentTsNum;
        auxiliary.auxiliaryOrder = beAided.auxiliaryOrder + 1;
        auxiliary.endPoint = [beAided auxiliaryEndPoint];//end要写在start前面,
        auxiliary.startPoint = [beAided auxiliaryStartPoint];
        auxiliary.dict_file = beAided.dict_file;
        
        [auxiliary auxiliaryStartDownload];//开始辅助下载;
        [self.debugView startShowWithIndex:[self.array_Ts indexOfObject:auxiliary]];
//        VCNSLog(@"要帮忙的%@ id = %@   帮忙的%@ ID = %@",beAided,[beAided.dict_file objectForKey:@"fileId"],auxiliary,[auxiliary.dict_file objectForKey:@"fileId"]);
    }else{//不需要辅助
//        VCNSLog(@"%@ 不要帮忙的",auxiliary);
        //如果不要辅助,那就继续下载新的
        if (self.downloadNum <= self.PlayNnm+3) {//判断当前下载到量比播放量还少
            VCNSLog(@"设置辅助下载属性");
            [self downloadWithTSNnm:self.downloadNum++ ts:auxiliary];
        }
    }
    
    
}

/**记录流量*/
-(void)recordFlowWiftFileDict:(VCDownloadTs *)Ts{
    self.vcSize += [[Ts.dict_file objectForKey:@"fileSize"] unsignedIntegerValue];
    
    for (NSMutableDictionary *dict_M in self.array_vc) {
        if ([[dict_M objectForKey:@"host"] isEqualToString:Ts.hostAndPort]) {
            NSUInteger tSize = [[dict_M objectForKey:@"tSize"] unsignedIntegerValue];//总流量
            tSize += Ts.tSize;
            NSUInteger vSize = [[dict_M objectForKey:@"vSize"] unsignedIntegerValue];//有效流量
            vSize += [[Ts.dict_file objectForKey:@"fileSize"] unsignedIntegerValue];
            [dict_M setObject:@(tSize) forKey:@"tSize"];
            [dict_M setObject:@(vSize) forKey:@"vSize"];
            break;
        }
    }
    
}
@end
